home *** CD-ROM | disk | FTP | other *** search
Text File | 2000-09-28 | 8.7 KB | 389 lines | [TEXT/MPS ] |
- %
- % File: HalftoneProcs.ps
- %
- % Contains: This file contains Procedures needed do the standard halftone dot types.
- %
- % Version: Technology: Quickdraw GX 1.1.x.
- %
- % Copyright: © 1991-7 by Apple Computer, Inc., all rights reserved.
- %
- %
-
- %
- % Procedure to generate the standard dispersed dot dither matrix.
- % Calculates the dither matrix by converting the shade to a base-4 number.
- % Each digit of the base 4 number represents a quadrant in the submatrix.
- % The submatrix for the least significant digit is the whole matrix,
- % this is divided into 4 submatrices for the next least significant and so on
- % down to a 2x2 cell submatrix for the most significant digit, made up of 1 cell
- % quadrants.
- %
- % size MakeDispDotMatrix matrix
- %
- % The size is the width of the matrix. Must be a power of 2.
- %
- /dispDotDict 12 dict dup begin % local variable dictionary for making the matrix.
-
- /dx [0 1 1 0] def
- /dy [0 1 0 1] def
- /size 0 def
- /nShades 0 def
- /theMatrix null def
- /lv 0 def
- /ilv 0 def
- /quadSize 0 def
- /quadrant 0 def
- /place 0 def
- /x 0 def
- /y 0 def
-
- end def
-
- /MakeDispDotMatrix {
-
- dispDotDict begin
-
- /dx [0 1 1 0] def % Arrays to determine quadrant position.
- /dy [0 1 0 1] def
-
- /size exch def % Get the size
- /nShades size size mul def % Get the number of shades we can dither
- /theMatrix nShades array def % Make an array for the dispersed dot matrix.
-
- 0 1 nShades 1 sub { % Loop from 0 to nShades-1
-
- /lv exch def % Get the current loop counter in lv (light-value)
- /ilv lv def % Grab a copy, we will manipulate this one.
-
- /place nShades 4 idiv def % Current base-4 place to calculate starts with n/4
- /quadSize 1 def % Quadrant size for most significant digit is 1 cell.
- /x 0 def /y 0 def % Initialize the matrix position
-
- % Calculate matrix position by offsets for each base-4 digit.
-
- {
- place 0 eq {exit} if % While place > 0
-
- /quadrant ilv place idiv def % The quadrant is the base-4 digit.
- /ilv ilv quadrant place mul sub def % Reduce the value to get the next digit later.
- /x x dx quadrant get quadSize mul add def % Calculate offset into quadrant (x+=dx[quadrant]*quadSize)
- /y y dy quadrant get quadSize mul add def % Do it for y also
- /place place 4 idiv def % Move to next most significant base-4 digit.
- /quadSize quadSize 2 mul def % Quadrant size doubles for each less significant digit.
-
- } loop
-
- theMatrix % Put the value in the matrix:
- y size mul x add % Calculate the index into the matrix based on x and y
- lv put
-
- } for
-
- end
-
- } Bdef
-
-
- %
- % Function computes a nearest power of two size for a matrix based upon the frequency
- % requested for the halftone.
- %
- % freq FrequencyToMatrixSize size
- %
- % freq: The requested frequency
- % size: the size of the dispersed dot matrix to use.
- /FrequencyToMatrixSize {
-
- 1 1 matrix defaultmatrix dtransform pop 72 mul abs % Get the resoultuion.
-
- exch div % This number is cell size in pixels for this frequency
-
- %
- % Now find the number that is nearest power of two to the cell size.
- %
- 0 5 { % Initialize n to 0, never go greater than 5 (yielding 32x32 cell - no point in doing so)
-
- dup 2 exch exp % Stack is now cell-size n 2^n
- 2 index % Stack is now cell-size n 2^n cell-size
- gt { % if 2^n > cellSize then
- exit % stop
- } if
-
- 1 add % increment n
-
- } repeat
-
- % We went one too many, subtract one.
-
- 1 sub
-
- exch pop % Get rid of the cell-size from the stack, leave the power of two to use.
-
- % raise 2 to the powere of size
-
- 2 exch exp cvi
-
- } Bdef
-
-
-
- %<FF>
- %
- % Make dictionary containing each of the 7 standard dot types.
- %
- /HalftoneDotFunctions 8 dict dup 3 -1 roll Xdef begin
-
- /TriangleDotFunction {
-
- Moby begin % Make sure Moby Dict is on stack, in case a postscript synonym executes currentscreen.
-
- 2 div /@2 Xdef % y / 2 (put into -0.5 to 0.5 range)
- dup 0 lt {neg} if 2 div /@1 Xdef % x = abs(x / 2)
-
- 2 @2 sub 2 @1 mul sub
-
- 2.5 div % Divide by maximum value
-
- end
-
- } Bdef
-
-
- /SpiralDotFunction {
-
- Moby begin % Make sure Moby Dict is on stack, in case a postscript synonym executes currentscreen.
-
- 2 div /@2 Xdef % y / 2 (put into -0.5 to 0.5 range)
- 2 div /@1 Xdef % x / 2 (put into -0.5 to 0.5 range)
-
- 1 @1 dup mul @2 dup mul @1 16 div @2 8 div add add add sub
-
- 1.1 div % The maxima skirts just above 1.0, so make sure PS doesn't
- % cause Rangecheck error.
-
- end
-
- } Bdef
-
-
- /SquareDotFunction {
-
- Moby begin % Make sure Moby Dict is on stack, in case a postscript synonym executes currentscreen.
-
- /@2 Xdef /@1 Xdef % Get x, y
-
- @1 @2 lt {@2} {@1} ifelse
-
- 1 exch sub
-
- 2 div % Divide by maximum value.
-
- end
-
- } Bdef
-
-
- /RoundDotFunction {
-
- Moby begin % Make sure Moby Dict is on stack, in case a postscript synonym executes currentscreen.
-
- abs /@2 Xdef % Save y
- abs /@1 Xdef % Save x
-
- @1 @2 add 1 gt {
-
- /@1 1 @1 sub def % subtract 1 from x and y
- /@2 1 @2 sub def
-
- @1 @1 mul
- @2 @2 mul
- add
- 1 sub
-
- } {
-
- 1
- @1 @1 mul
- @2 @2 mul
- sub
- sub
-
- } ifelse
-
- 2 div % Scale to fit in range.
-
- end
-
- } Bdef
-
-
- /EllipticDotFunction {
-
- Moby begin % Make sure Moby Dict is on stack, in case a postscript synonym executes currentscreen.
-
- /@2 Xdef
- /@1 Xdef
-
- /@2 @2 2 mul abs def % y = abs(2*y)
- /@1 @1 @1 mul def % x = x*x
- /@1 @1 @2 add def % x = x + y
- /@1 @1 3 div def % x = x/3
- 1 @1 sub
-
- 2 div % Scale to keep result between 0 and 1.
-
- end
-
- } Bdef
-
-
-
-
- /LineDotFunction {
-
- % This one does not require Moby dict to be on stack.
-
- exch pop
-
- } Bdef
-
-
-
- /DispersedDotFunction {
-
- Moby begin % Make sure Moby Dict is on stack, in case a postscript synonym executes currentscreen.
-
- dispDotDict begin
-
- % Use the coordintes passed to to index the matrix.
-
- 1 add 2 div size mul cvi exch % input is -1 ≤ x < 1, make: 0 ≤ x ≤ (size-1)
- 1 add 2 div size mul cvi exch % Do the same for y.
-
- size mul add % index = x * size + y
- theMatrix exch get % get theMatrix[index]
-
- nShades div % scale from 0-1 instead of from 0-nShades
-
- end
-
- end
-
- } Bdef
-
-
- end % defined dictionary for all halftone spot functions.
-
-
-
-
-
- %<FF>
- %
- %
- % SetHalftoneParams:
- %
- % Set up the current halftone on the printer:
- %
- % freq1 angle1 dotFunction1… freqN angleN dotFunctionN N SetHalftoneParams -
- %
- % freq1…N: Frequencies for components 1 through N
- % angle1…N: angles for components 1 through N
- % dotFunction1…N: names of dot functions 1 through N
- %
- % N: Number of color components allowed (1 or 4)
- %
- /SetHalftoneParams {
-
- 1 eq {
-
- dup /DispersedDotFunction eq {
-
- % Set up to do dispsersed dot function
-
- 2 index % Get the frequency
- FrequencyToMatrixSize % Compute the matrix size to use.
- MakeDispDotMatrix % Make the matrix in the dispDotDict dictionary.
-
- } if
-
- HalftoneDotFunctions exch get setscreen
-
- } { % must be 4 planes
-
- 4 {
-
- dup /DispersedDotFunction eq {
-
- % Set up to do dispersed dot function
- % The matrix that will end up being used will actually
- % be the one for the first of the components that requested DispersedDotFunction
-
- 2 index % Get the frequency
- FrequencyToMatrixSize % Compute the matrix size to use.
- MakeDispDotMatrix % Make the matrix in the dispDotDict dictionary.
-
- } if
-
- HalftoneDotFunctions exch get
- 12 3 roll
-
- } repeat
-
- %
- % If setcolorscreen exists, use it - else do a setscreen and pop the extra parameters
- %
- systemdict /setcolorscreen known {setcolorscreen} {setscreen 9 {pop} repeat} ifelse
-
- } ifelse
-
- } Bdef
-
- %<FF>
- %
- % Save the set of default halftone parameters.
- %
- languagelevel 2 lt { % for level-1, get current screen or color screen
-
- /DefineDefaultHalftone {
-
- /DefaultHalftone [
-
-
- systemdict /setcolorscreen known
- {currentcolorscreen} % If printer has color extensions, get color screen
- {currentscreen} % else get black and white screen.
- ifelse
-
- ] def
-
- } Bdef
-
- systemdict /setcolorscreen known {
-
- /SetDefaultHalftone {
-
- DefaultHalftone {} forall setcolorscreen
-
- } Bdef
-
- } {
-
- /SetDefaultHalftone {
-
- DefaultHalftone {} forall setscreen
-
- } Bdef
-
- } ifelse
-
- } { % For level-2, it is much easier, just get and set halftone dictionary.
-
- /DefineDefaultHalftone {/DefaultHalftone currenthalftone def} Bdef
-
- /SetDefaultHalftone {DefaultHalftone sethalftone} Bdef
-
- } ifelse
-
-
-